//  BLEHelper.m
//  SiterLib
//
//  Created by tracyhenry on 2022/12/20.
//
//
//Error code =            1009 //手机蓝牙服务未打开
//                        1100 //蓝牙权限未打开
//                        1102 //未发现蓝牙设备
//                        1103 //不支持的状态，可能蓝牙距离太远通讯异常
//                        1104 //不支持的服务和属性(可能是非法设备)
//                        1105 //发送第一次空握手无应答
//                        1106 //发送ssid后设备无应答
//                        1107 //发送Pincode后设备无应答
//                        1108 //第一次握手设备应答数据错误,可能是sn为空
//                        1109 //第二次握手设备应答数据错误
//                        1110 //第三次握手设备应答数据错误
//                        1111 //ssid为空
//                        1112 //设备联网超时，请确认设备联网状态
//                        1113 //蓝牙连接不上

#define  filterContent @"Siter"
#define  shadowName @"shadowName"
#define topicFromDev @"st/siterlink/%@/things/%@/from_dev"
#define topicToDev @"st/siterlink/%@/things/%@/to_dev"

typedef enum : NSUInteger{
    BLEConnInit = 0,
    BLEConnSelectDevice,
    BLEConnSendShakeOneComplete,
    BLEConnSendSSidComplete,
    BLEConnSendPincodeComplete,
} BLEConnStatus;

#import "BLEHelper.h"
#import <CoreBluetooth/CoreBluetooth.h>
#import "BlufiClient.h"
#import "SiterHelp.h"
#import "Single.h"
#import "NSString+CY.h"
#import "SiterAPI.h"
#import "EventData.h"
#import <AWSIoT/AWSIoTDataManager.h>
#import <AWSIoT/AWSIoTMessage.h>
#import "SiterAPI.h"
#import "NVLogManager.h"
#import "DeviceUtil.h"
#import "GetThingShadowApi.h"

@interface BLEHelper ()<CBCentralManagerDelegate,CBPeripheralDelegate,BlufiDelegate>

@property (nonatomic, strong) id<BLEDelegate> bledelegate;

// 中心管理者(管理设备的扫描和连接)
@property (nonatomic, strong) CBCentralManager *centralManager;
// 存储的设备
@property (nonatomic, strong) NSMutableArray *peripherals;

// 外设状态
@property (nonatomic, assign) CBManagerState peripheralState;

@property (nonatomic,strong) BlufiClient *blufiClient;

@property(nonatomic, strong) NSMutableArray *array_device;

@property(nonatomic, strong)NSTimer *timer;

@property(nonatomic,assign)int count;

@property(nonatomic, strong) Peripheral *connectedDevice;

@property(assign, atomic)BLEConnStatus bleconnStatus;

@property(copy, nonatomic)NSString * ssid;

@property(copy, nonatomic)NSString * pwd;

@property(strong,nonatomic)NSURLSessionDataTask *getNewDeviceListTask;

@property(copy,nonatomic)NSString *pincode;

@property(nonatomic,strong)NSDictionary * productList;

@property(nonatomic,strong)GetThingShadowApi *getThingShadowapi;
@end

@implementation BLEHelper

-(instancetype)initWithDelegate:(id<BLEDelegate>) delegate{
    if(self = [super init]){
        self.bledelegate = delegate;
        self.blufiClient = [[BlufiClient alloc] init];
        self.blufiClient.centralManagerDelete = self;
        self.blufiClient.peripheralDelegate = self;
        self.blufiClient.blufiDelegate = self;
    }
    return self;
}

- (void)BLEHelperInit {
    self.centralManager = [[CBCentralManager alloc]initWithDelegate:self queue:nil];
    self.bleconnStatus = BLEConnInit;
}


- (NSMutableArray *)array_device {
    if (!_array_device) {
        _array_device = [[NSMutableArray alloc] init];
    }
    return _array_device;
}

-(NSDictionary *)productList{
    if(_productList==nil){
        NSDictionary *dic1 = @{@"0001":@"GS368",@"0002":@"GS888W",@"0003":@"GS886W",@"1001":@"GS198"};
        _productList = [[NSDictionary alloc] initWithDictionary:dic1];
    }
    return _productList;
}

-(NSString *)pincode{
    if(_pincode==nil){
        _pincode = [self randomStringWithNumber:6];
        NVLogInfo(@"生成pincode:%@",_pincode);
    }
    return _pincode;
}

//随机字母
- (NSString *)randomStringWithNumber:(NSInteger)number{ //number 是需要的个数
    NSString *ramdom;
    NSMutableArray *array = [NSMutableArray array];
    for (int i = 1; i ; i ++) {
    int a = (arc4random() % 122); //如需要可以改变数值大小  这儿的数值是ASCII值
    if (a > 96) { //这儿是小写字母 如需要自行更改
        char c = (char)a;
        [array addObject:[NSString stringWithFormat:@"%c",c]];
        if (array.count == number) {
            break;
        }
    } else continue;
    }
    ramdom = [array componentsJoinedByString:@""];//这个是把数组转换为字符串
    return ramdom;
}

#pragma mark ---- method
- (void)stopScan {
    [self.array_device removeAllObjects];
    self.array_device = nil;
    [self endTimer];
    [self.centralManager stopScan];
}

- (void)startScan:(NSString *)ssid withPwd:(NSString *)pwd{
    
    self.ssid = ssid;
    self.pwd = pwd;
    if([NSString isBlankString:ssid]){
        long errerCode = [NSString isBlankString:ssid]?1111:1112;
        if(self.bledelegate && [self.bledelegate respondsToSelector:@selector(dueWithErr:)]){
            NSError *error = [[NSError alloc] initWithDomain:NSCocoaErrorDomain code:errerCode userInfo:nil];
            [self.bledelegate dueWithErr:error];
        }
        [self onDisconnected];
        [self stopScan];
        [self unSubscribeToMqtt];
        return;
    }
    
    self.centralManager = [[CBCentralManager alloc]initWithDelegate:self queue:nil];
    self.bleconnStatus = BLEConnInit;
    if (@available(iOS 10.0, *)) {
        if (self.peripheralState ==  CBManagerStatePoweredOn)
        {
            [self.centralManager scanForPeripheralsWithServices:nil options:nil];
        }
    } else {
        // Fallback on earlier versions
        [self.centralManager scanForPeripheralsWithServices:nil options:nil];
    }
}


-(NSString *)getNowTime{
    
    NSTimeZone* destinationTimeZone = [NSTimeZone localTimeZone] ;///获取当前时区信息
    NSInteger sourceGMTOffset = [destinationTimeZone secondsFromGMTForDate:[NSDate date]];///获取偏移秒数
    NSInteger zoneOffset = sourceGMTOffset/3600;
    NSInteger zoneOffsetMin = sourceGMTOffset/60;
    NSString *zone = @"00";
    if(zoneOffset<0){
        zoneOffset = 12 - zoneOffset;
    }
    
    int de = abs((int)zoneOffset);
    int deMin = abs((int)zoneOffsetMin%60);
    NSString *time = [NSString stringWithFormat:@"%02d",de];
    NSString *timeMin =  [NSString stringWithFormat:@"%02d",deMin];;
    
    
    return [NSString stringWithFormat:@"%@%@%@",zone,time,timeMin];
}


-(void)setConnectDevice:(nonnull Peripheral *)device{
    NVLogInfo(@"连接蓝牙哈哈");
    self.connectedDevice = device;
    if(_blufiClient==nil){
        _blufiClient = [[BlufiClient alloc] init];
        _blufiClient.centralManagerDelete = self;
        _blufiClient.peripheralDelegate = self;
        _blufiClient.blufiDelegate = self;
    }
    [_blufiClient connect:self.connectedDevice.uuid.UUIDString];
}



- (void)onDisconnected {
    self.bleconnStatus = BLEConnInit;
    if (_blufiClient) {
        [_blufiClient close];
    }
}

-(void)disconnect {
    [self onDisconnected];
    [self stopScan];
    [self unSubscribeToMqtt];
    self.centralManager = nil;
    if(self.getNewDeviceListTask!=nil){
        [self.getNewDeviceListTask cancel];
        self.getNewDeviceListTask = nil;
    }
    self.pincode = nil;
}

-(void)startTimer{
    self.count = 0;
    if(_timer!=nil){
        [_timer invalidate];
    }
    _timer = [NSTimer scheduledTimerWithTimeInterval:1.0 target:self selector:@selector(runTimer) userInfo:nil repeats:YES];
    [[NSRunLoop currentRunLoop] addTimer:_timer forMode:UITrackingRunLoopMode];
}

-(void)endTimer{
    self.getThingShadowapi = nil;
    self.count = 0;
    if(_timer!=nil){
        [_timer invalidate];
    }
    _timer = nil;
}

-(void)runTimer{
    
    self.count++;
    int count_max = 6;
    switch(self.bleconnStatus){
        case BLEConnInit:
            count_max= 20;
            break;
        case BLEConnSelectDevice:
            count_max=6;
            break;
        case BLEConnSendShakeOneComplete:
            count_max=6;
            break;
        case BLEConnSendSSidComplete:
            count_max=18;
            break;
        case BLEConnSendPincodeComplete:
            count_max=120;
            break;
    }
    if(self.count>=count_max){
        self.count = 0;
        switch(self.bleconnStatus){
            case BLEConnInit:
                if(self.bledelegate && [self.bledelegate respondsToSelector:@selector(dueWithErr:)]){
                    NSError *error = nil;
                    if(self.connectedDevice==nil){
                        error = [[NSError alloc] initWithDomain:NSCocoaErrorDomain code:1102 userInfo:nil];
                    }else{
                        error = [[NSError alloc] initWithDomain:NSCocoaErrorDomain code:1113 userInfo:nil];
                    }
                    [self.bledelegate dueWithErr:error];
                }
                [self onDisconnected];
                [self stopScan];
                [self unSubscribeToMqtt];
                break;
            case BLEConnSelectDevice:
                //重发ssid
                if(self.bledelegate && [self.bledelegate respondsToSelector:@selector(dueWithErr:)]){
                    NSError *error = [[NSError alloc] initWithDomain:NSCocoaErrorDomain code:1105 userInfo:nil];
                    [self.bledelegate dueWithErr:error];
                }
                [self onDisconnected];
                [self stopScan];
                [self unSubscribeToMqtt];
                break;
            case BLEConnSendShakeOneComplete:
                if(self.bledelegate && [self.bledelegate respondsToSelector:@selector(dueWithErr:)]){
                    NSError *error = [[NSError alloc] initWithDomain:NSCocoaErrorDomain code:1106 userInfo:nil];
                    [self.bledelegate dueWithErr:error];
                }
                [self onDisconnected];
                [self stopScan];
                [self unSubscribeToMqtt];
                break;
            case BLEConnSendSSidComplete:
                if(self.bledelegate && [self.bledelegate respondsToSelector:@selector(dueWithErr:)]){
                    NSError *error = [[NSError alloc] initWithDomain:NSCocoaErrorDomain code:1107 userInfo:nil];
                    [self.bledelegate dueWithErr:error];
                }
                [self onDisconnected];
                [self stopScan];
                [self unSubscribeToMqtt];
                break;
            case BLEConnSendPincodeComplete:
                //重发http绑定接口
                if(self.bledelegate && [self.bledelegate respondsToSelector:@selector(dueWithErr:)]){
                    NSError *error = [[NSError alloc] initWithDomain:NSCocoaErrorDomain code:1112 userInfo:nil];
                    [self.bledelegate dueWithErr:error];
                }
                [self onDisconnected];
                [self stopScan];
                [self unSubscribeToMqtt];
                break;
        }
        
    }else{
        switch(self.bleconnStatus){
            case BLEConnInit:
                if(self.connectedDevice!=nil&&self.count%5==0){
                    NVLogInfo(@"连接蓝牙哈哈");
                    [_blufiClient connect:self.connectedDevice.uuid.UUIDString];
                }
                break;
            case BLEConnSelectDevice:
                //重发第一次握手
                [self sendInfo:[self getFirstShakeInfo]];
                break;
            case BLEConnSendShakeOneComplete:
                //重发ssid
                [self sendInfo:[self getSSidInfo]];
                break;
            case BLEConnSendSSidComplete:
                //重发pincode
                if(_count%6==0){
                    [self sendInfo:[self getPincodeInfo]];
                }
                break;
            case BLEConnSendPincodeComplete:
                [self getShadow];
                break;
            default:
                break;
        }
    }
    
    
}


-(NSData *)getFirstShakeInfo{
    NSDictionary *dic = @{
            @"cmd":@0,
            @"str1":@"",
            @"str2":@"",
            @"str3":@"",
    };
    NVLogInfo(@"发送第一次shake包:%@",dic);
    return [self convertToJsonData:dic];
}


-(NSData *)getSSidInfo{
    
    NSDictionary *dic = @{
            @"cmd":@1,
            @"str1":[NSString isBlankString:self.ssid]?@"":self.ssid,
            @"str2":[NSString isBlankString:self.pwd]?@"":self.pwd,
            @"str3":[self getNowTime],
    };
    NVLogInfo(@"发送ssid信息:%@",dic);
    return [self convertToJsonData:dic];
}

-(NSData *)getPincodeInfo{
    
    NSString *prodkey = self.connectedDevice.productKey;
    if([NSString isBlankString:prodkey]||[@"GS368" isEqualToString:prodkey]){
        prodkey = shadowName;
    }
    
    NSDictionary *dic = @{
            @"cmd":@2,
            @"str1": [NSString stringWithFormat:@"%@",[Siter sharedInstance].uid],
            @"str2":prodkey,
            @"str3":[NSString isBlankString:self.pincode]?@"":self.pincode
    };
    NVLogInfo(@"发送Pincode信息:%@",dic);
    return [self convertToJsonData:dic];
}


-(NSString *)respondToBindOK{
    
    NSDictionary *dic = @{
            @"cmd":@65531,
            @"str1":@"bindOK",
            @"str2":@"",
            @"str3":@"",
    };
    NVLogInfo(@"发送bindOK应答:%@",dic);
    return [self convertToJsonString:dic];
}


- (NSData *)convertToJsonData:(NSDictionary *) dict {
    NSError *error;
    NSData *jsonData = [NSJSONSerialization dataWithJSONObject:dict
                                        options:NSJSONWritingSortedKeys
                                        error:&error];
    NSString *jsonString;
    if (!jsonData) {
        NVLogInfo(@"%@",error);
    } else {
        jsonString = [[NSString alloc]initWithData:jsonData encoding:NSUTF8StringEncoding];
    }
    
    NVLogInfo(@"发送包:%@",jsonString);
    NSData* data = [jsonString dataUsingEncoding:NSUTF8StringEncoding];
    
    return data;
}

-(NSString *)convertToJsonString:(NSDictionary *)dict{
    NSError *error;
    NSData *jsonData = [NSJSONSerialization dataWithJSONObject:dict options:NSJSONWritingPrettyPrinted error:&error];
    NSString *jsonString;
    
    if (!jsonData) {
        NVLogInfo(@"%@",error);
    }else{
        jsonString = [[NSString alloc]initWithData:jsonData encoding:NSUTF8StringEncoding];
    }
    NSMutableString *mutStr = [NSMutableString stringWithString:jsonString];
    
    NSRange range = {0,jsonString.length};
    
    [mutStr replaceOccurrencesOfString:@" " withString:@"" options:NSLiteralSearch range:range];
    NSRange range2 = {0,mutStr.length};
    [mutStr replaceOccurrencesOfString:@"\n" withString:@"" options:NSLiteralSearch range:range2];
    return mutStr;
    
}



-(void)sendInfo:(NSData *)info{
    if(self.blufiClient){
        [self.blufiClient postCustomData:info];
    }
}

-(void)subscribeToMqtt{
    if(![NSString isBlankString:self.connectedDevice.productKey]&&![NSString isBlankString:self.connectedDevice.thingName]&&[Siter sharedInstance].uid!=nil){
        NSString *topic = [NSString stringWithFormat:topicFromDev,[Siter sharedInstance].uid,self.connectedDevice.thingName];
        NVLogInfo(@"订阅监听:%@",topic);
        [[AWSIoTDataManager IoTDataManagerForKey:[[Siter sharedInstance] getAWSIOTDATAMANAGERKEY]] subscribeToTopic:topic QoS:AWSIoTMQTTQoSMessageDeliveryAttemptedAtLeastOnce fullCallback:^(NSString * _Nonnull topic, AWSIoTMessage * _Nonnull message) {
            NVLogInfo(@"收到绑定确认数据:%@",message.message);
            EventData *eventData = [[EventData alloc] initWithString:message.message error:nil];
            if(eventData!=nil){
                if([eventData.event_details.cmd intValue]==65531&&[@"bindOK?" isEqualToString:eventData.event_details.str1]){
                    
                    [[AWSIoTDataManager IoTDataManagerForKey:[[Siter sharedInstance] getAWSIOTDATAMANAGERKEY]] publishString:[self respondToBindOK] onTopic:[NSString stringWithFormat:topicToDev,[Siter sharedInstance].uid,self.connectedDevice.thingName] QoS:AWSIoTMQTTQoSMessageDeliveryAttemptedAtLeastOnce];
                    
                    
                    if(self.bledelegate && [self.bledelegate respondsToSelector:@selector(bindDeviceModel:)]){
                        [self endTimer];
                        [self.bledelegate bindDeviceModel:[NSString stringWithFormat:@"%@",self.connectedDevice.thingName]];
                    }
                }
            }
            [self unSubscribeToMqtt];
        }];
    }

}

-(void)unSubscribeToMqtt{
    if(self.connectedDevice!=nil){
        if(![NSString isBlankString:self.connectedDevice.productKey]&&![NSString isBlankString:self.connectedDevice.thingName]&&[Siter sharedInstance].uid!=nil){
            NSString *topic = [NSString stringWithFormat:topicFromDev,[Siter sharedInstance].uid,self.connectedDevice.thingName];
            [[AWSIoTDataManager IoTDataManagerForKey:[[Siter sharedInstance] getAWSIOTDATAMANAGERKEY]] unsubscribeTopic:topic];
            self.connectedDevice = nil;
        }
    }
}

#pragma mark ---- delegate
/**
 扫描到设备
 
 @param central 中心管理者
 @param peripheral 扫描到的设备
 @param advertisementData 广告信息
 @param RSSI 信号强度
 */
- (void)centralManager:(CBCentralManager *)central didDiscoverPeripheral:(CBPeripheral *)peripheral advertisementData:(NSDictionary<NSString *,id> *)advertisementData RSSI:(NSNumber *)RSSI {
    Peripheral *device = [[Peripheral alloc] initWithPeripheral:peripheral];
    device.name = [advertisementData objectForKey:@"kCBAdvDataLocalName"];
    device.rssi = RSSI.intValue;
    
    if ([DeviceUtil shouldAddToSource:device withArrary:self.array_device]&&self.connectedDevice==nil) {
        [self.array_device addObject:device];
        if(self.bledelegate && [self.bledelegate respondsToSelector:@selector(findMULBLEDevice:)]){
            [self.bledelegate findMULBLEDevice:self.array_device];
        }
    }
}


// 状态更新时调用
- (void)centralManagerDidUpdateState:(CBCentralManager *)central
{
    switch (central.state) {
        case CBManagerStateUnknown:{
            NVLogInfo(@"status->:未知状态");
            self.peripheralState = central.state;
            NSError *error = [[NSError alloc] initWithDomain:NSCocoaErrorDomain code:1103 userInfo:nil];
            if(self.bledelegate && [self.bledelegate respondsToSelector:@selector(dueWithErr:)]){
                [self.bledelegate dueWithErr:error];
            }
            [self onDisconnected];
            [self stopScan];
            [self unSubscribeToMqtt];
        }
            break;
        case CBManagerStateResetting:
        {
            NVLogInfo(@"status->:重置状态");
            self.peripheralState = central.state;
            if(self.bledelegate && [self.bledelegate respondsToSelector:@selector(dueWithErr:)]){
                NSError *error = [[NSError alloc] initWithDomain:NSCocoaErrorDomain code:1103 userInfo:nil];
                [self.bledelegate dueWithErr:error];
            }
            [self onDisconnected];
            [self stopScan];
            [self unSubscribeToMqtt];
        }
            break;
        case CBManagerStateUnsupported:
        {
            NVLogInfo(@"status->:不支持的状态");
            self.peripheralState = central.state;
            if(self.bledelegate && [self.bledelegate respondsToSelector:@selector(dueWithErr:)]){
                NSError *error = [[NSError alloc] initWithDomain:NSCocoaErrorDomain code:1103 userInfo:nil];
                [self.bledelegate dueWithErr:error];
            }
            [self onDisconnected];
            [self stopScan];
            [self unSubscribeToMqtt];
        }
            break;
        case CBManagerStateUnauthorized:
        {
            NVLogInfo(@"status->:未授权的状态");
            self.peripheralState = central.state;
            if(self.bledelegate && [self.bledelegate respondsToSelector:@selector(dueWithErr:)]){
                NSError *error = [[NSError alloc] initWithDomain:NSCocoaErrorDomain code:1100 userInfo:nil];
                [self.bledelegate dueWithErr:error];
            }
            [self onDisconnected];
            [self stopScan];
            [self unSubscribeToMqtt];
        }
            break;
        case CBManagerStatePoweredOff:
        {
            NVLogInfo(@"status->:关闭状态");
            self.peripheralState = central.state;
            if(self.bledelegate && [self.bledelegate respondsToSelector:@selector(dueWithErr:)]){
                NSError *error = [[NSError alloc] initWithDomain:NSCocoaErrorDomain code:1009 userInfo:nil];
                [self.bledelegate dueWithErr:error];
            }
            [self onDisconnected];
            [self stopScan];
            [self unSubscribeToMqtt];
        }
            break;
        case CBManagerStatePoweredOn:
        {
            NVLogInfo(@"status->:开启状态－可用状态");
            self.peripheralState = central.state;
            NVLogInfo(@"%ld",(long)self.peripheralState);
            if(self.bledelegate && [self.bledelegate respondsToSelector:@selector(blueToothAvailable)]){
                [self.bledelegate blueToothAvailable];
            }
            
            if(self.bleconnStatus==BLEConnInit){
                [self.centralManager scanForPeripheralsWithServices:nil options:nil];
                [self startTimer];
            }
        }
            break;
        default:
            break;
    }
}


-(void)centralManager:(CBCentralManager *)central didDisconnectPeripheral:(CBPeripheral *)peripheral error:(NSError *)error{
    NVLogInfo(@"蓝牙连接断开");
}

-(void)blufi:(BlufiClient *)client didPostCustomData:(NSData *)data status:(BlufiStatusCode)status{
    
}


-(void)blufi:(BlufiClient *)client didReceiveCustomData:(NSData *)data status:(BlufiStatusCode)status{
    NSString *customString = [[NSString alloc] initWithData:data encoding:NSUTF8StringEncoding];
    NSLog(@"Receive device custom data: %@",customString);
    EventData *eventData = [[EventData alloc] initWithData:data error:nil];
    
    if(eventData==nil) return;
    
    if(self.bleconnStatus == BLEConnSelectDevice){
        NSString *sn = eventData.event_details.str3;
        if([eventData.event_details.cmd intValue]==0&&![NSString isBlankString:sn]){
            self.bleconnStatus = BLEConnSendShakeOneComplete;
            NSString *de = eventData.event_details.str1;
            NSString *str2 = eventData.event_details.str2;
            NSString *str3 = eventData.event_details.str3;
            if(de.length>=16){
                NSString *de1 = [de substringWithRange:NSMakeRange(10, 4)];
                NSString *device_stats = [de substringWithRange:NSMakeRange(14, 2)];
                
                if([de1 isEqualToString:@"0001"] ){
                    NSString *mac = [str2 stringByAppendingString:str3];
                    [self.connectedDevice setThingName:mac];
                }else{
                    if([device_stats isEqualToString:@"00"]){
                        NSString *mac = [str3 stringByAppendingString:str2];
                        [self.connectedDevice setThingName:mac];
                    }else{
                        [self.connectedDevice setThingName:str3];
                    }
                }
                

                [self.connectedDevice setProductKey:[self.productList objectForKey:de1]];
            }
     
            [self sendInfo:[self getSSidInfo]];
            [self startTimer];
            [self subscribeToMqtt];
        }else{
            if(self.bledelegate && [self.bledelegate respondsToSelector:@selector(dueWithErr:)]){
                NSError *error = [[NSError alloc] initWithDomain:NSCocoaErrorDomain code:1108 userInfo:nil];
                [self.bledelegate dueWithErr:error];
            }
            [self onDisconnected];
            [self stopScan];
            [self unSubscribeToMqtt];
        }
    }else if(self.bleconnStatus==BLEConnSendShakeOneComplete){
        if([eventData.event_details.cmd intValue]==1){
            self.bleconnStatus = BLEConnSendSSidComplete;
            [self sendInfo:[self getPincodeInfo]];
            [self startTimer];
        }else{
            if(self.bledelegate && [self.bledelegate respondsToSelector:@selector(dueWithErr:)]){
                NSError *error = [[NSError alloc] initWithDomain:NSCocoaErrorDomain code:1109 userInfo:nil];
                [self.bledelegate dueWithErr:error];
            }
            [self onDisconnected];
            [self stopScan];
            [self unSubscribeToMqtt];
        }
    }else if(self.bleconnStatus==BLEConnSendSSidComplete){
        if([eventData.event_details.cmd intValue]==2){
            self.bleconnStatus = BLEConnSendPincodeComplete;
            if(self.bledelegate && [self.bledelegate respondsToSelector:@selector(shakeHandsEnd:)]){
                [self.bledelegate shakeHandsEnd:self.connectedDevice.thingName];
            }
            [self startTimer];
            if (_blufiClient) {
                [_blufiClient close];
            }
        }else{
            if(self.bledelegate && [self.bledelegate respondsToSelector:@selector(dueWithErr:)]){
                NSError *error = [[NSError alloc] initWithDomain:NSCocoaErrorDomain code:1110 userInfo:nil];
                [self.bledelegate dueWithErr:error];
            }
            [self onDisconnected];
            [self stopScan];
            [self unSubscribeToMqtt];
        }
    }
}


-(void)blufi:(BlufiClient *)client didReceiveError:(NSInteger)errCode{
    NVLogInfo(@"didReceiveError: %zd",errCode);
    if(self.bledelegate && [self.bledelegate respondsToSelector:@selector(dueWithErr:)]){
        NSError *error = [[NSError alloc] initWithDomain:NSCocoaErrorDomain code:1103 userInfo:nil];
        [self.bledelegate dueWithErr:error];
    }
    [self onDisconnected];
    [self stopScan];
    [self unSubscribeToMqtt];
}


-(void)blufi:(BlufiClient *)client gattPrepared:(BlufiStatusCode)status service:(CBService *)service writeChar:(CBCharacteristic *)writeChar notifyChar:(CBCharacteristic *)notifyChar{
    if (status == StatusSuccess) {
        self.bleconnStatus = BLEConnSelectDevice;
        NVLogInfo(@"BluFi connection has prepared");
        [self sendInfo:[self getFirstShakeInfo]];
        [self startTimer];
    } else {
        if (!service) {
            NVLogInfo(@"Discover service failed");
        } else if (!writeChar) {
            NVLogInfo(@"Discover write char failed");
        } else if (!notifyChar) {
            NVLogInfo(@"Discover notify char failed");
        }
        if(self.bledelegate && [self.bledelegate respondsToSelector:@selector(dueWithErr:)]){
            NSError *error = [[NSError alloc] initWithDomain:NSCocoaErrorDomain code:1104 userInfo:nil];
            [self.bledelegate dueWithErr:error];
        }
        [self onDisconnected];
        [self stopScan];
        [self unSubscribeToMqtt];
    }
}


#pragma mark -GetShaodw
-(void)getShadow{
    self.getThingShadowapi = [[GetThingShadowApi alloc] initWithDevId:self.connectedDevice.thingName withThingTypeName:self.connectedDevice.productKey];
    [self.getThingShadowapi startSend:^(NSError *error, id response) {
        NSDictionary *dic = response;
        NSString *receive_pincode = dic[@"state"][@"reported"][@"pincode"];
        NVLogInfo(@"获取到影子里的pincode:%@",receive_pincode);
        if([receive_pincode isEqualToString:self.pincode]&&![NSString isBlankString:self.pincode]){
            if(self.bledelegate && [self.bledelegate respondsToSelector:@selector(bindDeviceModel:)]){
                [self endTimer];
                [self.bledelegate bindDeviceModel:[NSString stringWithFormat:@"%@",self.connectedDevice.thingName]];

            }
        }
    }];
}

@end
